home *** CD-ROM | disk | FTP | other *** search
/ System Booster / System Booster.iso / Texteditors / Origami / Sources / src / origami / fieldedit.c < prev    next >
Encoding:
C/C++ Source or Header  |  1996-09-27  |  25.9 KB  |  851 lines

  1. /*{{{}}}*/
  2. /*{{{  #includes*/
  3. #ifdef CONFIG_H
  4. #   include "config.h"
  5. #endif
  6.  
  7. #include <sys/types.h>
  8. #include <unistd.h>
  9. #include <ctype.h>
  10. #include <limits.h>
  11. #include <string.h>
  12. #include <signal.h>
  13. #include <stdlib.h>
  14. #include <stdio.h>
  15.  
  16. #define FIELDEDIT_C
  17. #define I_BUFFLOOP_C
  18. #define I_DISPLAY_C
  19. #define I_FILEC_C
  20. #define I_FOLDING_C
  21. #define I_GETTK_C
  22. #define I_GETMSG_C
  23. #define I_KEYTAB_C
  24. #define I_LOOP_C
  25. #define I_MAIN_C
  26. #define I_MESSAGES_C
  27. #define I_ORIEDT_C
  28. #define I_PROMPT_C
  29. #define I_SCREEN_C
  30. #define I_SET_C
  31. #define I_SIGNALS_C
  32. #define I_STRING_C
  33. #define I_VIRTUAL_C
  34.  
  35. #include "origami.h"
  36. #include <lib/ori_add_lib.h>
  37. /*}}}  */
  38.  
  39. /*{{{  variables*/
  40. private unsigned char curr_c=' ';
  41. private int ind;
  42. private int txt_pos;
  43. private int txt_len;
  44. private int f_txt_offset=0;
  45. private int high_lim= -1;
  46. private highlight_typ high_type=no_highlight;
  47. public unsigned char deleted_ch = ' ';
  48. /*}}}  */
  49.  
  50. /*{{{  field_scr2txt*/
  51. private int field_scr2txt(int o,int x,unsigned char const * const s)
  52. { int txt;
  53.  
  54.   txt=scr2txt(o,x,s);
  55.   if (txt>txt_len)
  56.      txt= -1;
  57.   return(txt);
  58. }
  59. /*}}}  */
  60. /*{{{  append_needed_spaces*/
  61. private void append_needed_spaces(boolean add_one)
  62. { if (txt_pos==-1 || txt_pos==txt_len)
  63.    { int i;
  64.      unsigned char *x;
  65.  
  66.      if (txt_pos==-1)
  67.         txt_pos=scr2txt(bd.f.enter_spaces,bd.scr.cursor.w,cur_dsp_line);
  68.      i=txt_pos-txt_len;
  69.      if (add_one)
  70.         i++;
  71.      x=cur_dsp_line+txt_len;
  72.      txt_len+=i;
  73.      memset(x,(int)' ',(size_t)i);
  74.      x[i]='\0';
  75.      if (dsp.norm!=norm_dsp)
  76.         bd.scr.cur_shift_w= -1;
  77.    }
  78. }
  79. /*}}}  */
  80. /*{{{  refresh_field*/
  81. private void refresh_field(int froms,boolean clr2eoln,boolean force)
  82. { int x;
  83.  
  84.   if (froms<1)
  85.      froms = 1;
  86.   x_shift
  87.    ( &bd.scr.cur_shift_w,
  88.      &f_txt_offset,
  89.      x=bd.scr.cur_shift_w,
  90.      bd.scr.cursor.w,
  91.      bd.f.enter_spaces,
  92.      cur_dsp_line
  93.    );
  94.   if (force || x!=bd.scr.cur_shift_w)
  95.    { froms=bd.scr.cur_shift_w+1;x=f_txt_offset; }
  96.   else
  97.      x=scr2txt(bd.f.enter_spaces,froms,cur_dsp_line);
  98.   if (x>=txt_len)
  99.    /*{{{  clr line from position*/
  100.    { if (clr2eoln)
  101.        clrbuffline(bd.scr.cursor.h,froms-bd.scr.cur_shift_w);
  102.    }
  103.    /*}}}  */
  104.   else
  105.    /*{{{  print line*/
  106.    { int p,h1,h2;
  107.  
  108.      move_cursor_to(bd.scr.cursor.h+bd.scr.off.h,froms-bd.scr.cur_shift_w+bd.scr.off.w);
  109.      /*{{{  get highlight positions*/
  110.      if (high_lim>=0)
  111.       { int l;
  112.  
  113.         l=(high_type==m_f_highlight)?bd.e.makefold_indent+1:bd.scr.cursor.w;
  114.         if (l>high_lim)
  115.          { h1=high_lim;h2=l-1; }
  116.         else
  117.          { h1=l-1;h2=high_lim+1;
  118.            if (h1<h2)
  119.               h1++;
  120.          }
  121.       }
  122.      else
  123.       { h1=(LINELEN+2)*max_dsp;
  124.         h2=(LINELEN+3)*max_dsp;
  125.       }
  126.      /*}}}  */
  127.      /*{{{  print the line*/
  128.      p=prt_highlight_bin_text
  129.         ( h1-froms+1,
  130.           h2-froms+1,
  131.           bd.f.enter_spaces+froms-1,
  132.           bd.scr.txt_size.w-froms+bd.scr.cur_shift_w,
  133.           True,
  134.           cur_dsp_line+x
  135.         );
  136.      /*}}}  */
  137.      /*{{{  maybe delete tail*/
  138.      if (clr2eoln && p<=bd.scr.txt_size.w-froms+bd.scr.cur_shift_w)
  139.         clrbuffline(bd.scr.cursor.h,froms-bd.scr.cur_shift_w+p);
  140.      /*}}}  */
  141.    }
  142.    /*}}}  */
  143.   if (bd.scr.cur_shift_w && soln_str)
  144.    { move_cursor_to(bd.scr.cursor.h+bd.scr.off.h,1+bd.scr.off.w);
  145.      oputc(soln_str);
  146.    }
  147. }
  148. /*}}}  */
  149. /*{{{  restore_cursor*/
  150. private void restore_cursor(boolean force)
  151.  { int x;
  152.  
  153.    /*{{{  get shift-width*/
  154.    ori_assert(bd.scr.cur_shift_w<=LINELEN*max_dsp,"shift-check");
  155.    x_shift
  156.     ( &x,
  157.       &f_txt_offset,
  158.       (x=bd.scr.cur_shift_w),
  159.       bd.scr.cursor.w,
  160.       bd.f.enter_spaces,
  161.       cur_dsp_line
  162.     );
  163.    /*}}}  */
  164.    /*{{{  maybe special screen update (highlight or full-shift)*/
  165.    if (force || x!=bd.scr.cur_shift_w || high_lim>=0)
  166.     { refresh_field(x+1,True,True);
  167.       title_op(CHGX);
  168.     }
  169.    /*}}}  */
  170.    title_op(UPDTITLE);
  171.    move_cursor_to
  172.     ( bd.scr.cursor.h+bd.scr.off.h,
  173.       (int)(1+(bd.scr.cursor.w-1-bd.scr.cur_shift_w)%bd.scr.txt_size.w)+bd.scr.off.w
  174.     );
  175.  }
  176. /*}}}  */
  177. /*{{{  restore_cursor_and_sleep*/
  178. public void restore_cursor_and_sleep(int t)
  179.  {
  180.    if (!scr_off)
  181.     { restore_cursor(False);
  182.       oflush;
  183.       if (t>=10)
  184.          sleep(t/10);
  185.       if ((t%=10))
  186.          usleep((unsigned int)t*(unsigned long)100000);
  187.     }
  188.  }
  189. /*}}}  */
  190. /*{{{  field_move_cursor*/
  191. private void field_move_cursor(int dist)
  192. { while (dist)
  193.     if (dist>0)
  194.      /*{{{  move right*/
  195.      { if (txt_pos==-1 || txt_pos==txt_len)
  196.         /*{{{  simple go right on screen*/
  197.         { bd.scr.cursor.w+=dist*dsp.norm;
  198.           txt_pos= -1;
  199.           dist=0;
  200.         }
  201.         /*}}}  */
  202.        else
  203.         /*{{{  maybe check if tab*/
  204.         { enum dsp_size dsp_lg;
  205.  
  206.           switch((dsp_lg=CHAR_DSP_SIZE(cur_dsp_line[txt_pos])))
  207.            { case tab_dsp:
  208.                 bd.scr.cursor.w=((bd.scr.cursor.w+bd.f.enter_spaces+dsp.tab_size-1)/dsp.tab_size)*dsp.tab_size+1-bd.f.enter_spaces;
  209.                 break;
  210.              case ictrl_dsp:
  211.                 dsp_lg=1;
  212.              default:
  213.                 bd.scr.cursor.w+=dsp_lg;
  214.                 break;
  215.            }
  216.           txt_pos++;
  217.           if (txt_pos>txt_len)
  218.              txt_pos= -1;
  219.           dist--;
  220.         }
  221.         /*}}}  */
  222.      }
  223.      /*}}}  */
  224.     else
  225.      /*{{{  move left*/
  226.      { if (txt_pos==-1)
  227.           txt_pos=scr2txt(bd.f.enter_spaces,bd.scr.cursor.w,cur_dsp_line);
  228.        txt_pos--;
  229.        if (txt_pos<txt_len)
  230.         /*{{{  check the given character too*/
  231.         { enum dsp_size dsp_lg;
  232.  
  233.           switch((dsp_lg=CHAR_DSP_SIZE(cur_dsp_line[txt_pos])))
  234.            { case tab_dsp:
  235.                 bd.scr.cursor.w=txt2scr(bd.f.enter_spaces,txt_pos,cur_dsp_line);
  236.                 break;
  237.              case ictrl_dsp:
  238.                 dsp_lg=1;
  239.              default:
  240.                 bd.scr.cursor.w-=dsp_lg;
  241.                 break;
  242.            }
  243.         }
  244.         /*}}}  */
  245.        else
  246.         /*{{{  char is ' '!*/
  247.           bd.scr.cursor.w-=dsp.norm;
  248.         /*}}}  */
  249.        dist++;
  250.      }
  251.      /*}}}  */
  252.   /*{{{  maybe overflow-controll*/
  253.   if (txt_pos>txt_len) txt_pos= -1;
  254.   if (bd.scr.cursor.w<=0) { bd.scr.cursor.w=1;txt_pos=0; }
  255.   if (bd.scr.cursor.w>LINELEN-bd.f.enter_spaces+1 )
  256.      if (scr2txt(bd.f.enter_spaces,bd.scr.cursor.w,cur_dsp_line)>LINELEN-bd.f.enter_spaces)
  257.       { bd.scr.cursor.w=LINELEN-bd.f.enter_spaces+1;
  258.         txt_pos=field_scr2txt(bd.f.enter_spaces,bd.scr.cursor.w,cur_dsp_line);
  259.         msg_message(M_LONG_LINE);
  260.       }
  261.   /*}}}  */
  262. }
  263. /*}}}  */
  264. /*{{{  move_cursor*/
  265. public void move_cursor(int dist)
  266. {
  267.   txt_len=ustrlen(cur_dsp_line);
  268.   txt_pos=field_scr2txt(bd.f.enter_spaces,bd.scr.cursor.w,cur_dsp_line);
  269.   field_move_cursor(dist);
  270. }
  271. /*}}}  */
  272. /*{{{  do_cc_compare*/
  273. public void do_cc_compare(unsigned char const c,TOKEN const tok)
  274. {
  275.   unsigned int a;
  276.  
  277.   a=get_arg("do-c-compare");
  278.   switch (tok)
  279.    { case M_TEST_CHAR_SET:
  280.         macro_tag=test_char_set(c,a);
  281.         break;
  282.      case M_TEST_CC:
  283.      case M_TEST_L_CC:
  284.      case M_TEST_H_CC:
  285.         a=ocl_var[a].v;
  286.      default:
  287.         macro_tag=
  288.            (tok==M_TEST_CHAR || tok==M_TEST_CC)      ? ((unsigned int)c==a) :
  289.            (tok==M_TEST_CHAR_LOW || tok==M_TEST_L_CC)? ((unsigned int)c<a) :
  290.                                                        ((unsigned int)c>a);
  291.    }
  292. }
  293. /*}}}  */
  294. /*{{{  do_str_compare*/
  295. public void do_str_compare(unsigned char const * const str)
  296.  { unsigned char arg[LINELEN+1];
  297.  
  298.    prompt_string(arg);
  299.    macro_tag=!strncmp((char*)str,(char*)arg,ustrlen(arg));
  300.  }
  301. /*}}}  */
  302. /*{{{  insert_*/
  303. private void insert_(char const ch)
  304. {
  305.   /*{{{  errorcheck && prepare*/
  306.   /*{{{  edit-position*/
  307.   if
  308.    (   (    bd.scr.cursor.w>bd.e.pre_scr_e_pos
  309.          || ch!=' '
  310.          || bd.scr.cursor.w<=ind*dsp.norm
  311.          || bd.m.overwrite
  312.        )
  313.     && bd.scr.cursor.w<bd.e.first_scr_e_pos
  314.    )
  315.    { verbose_msg_message(M_ERR_PO);
  316.      goto unchange_ret;
  317.    }
  318.   if (bd.scr.cursor.w>LINELEN-bd.f.enter_spaces)
  319.      if (scr2txt(bd.f.enter_spaces,bd.scr.cursor.w,cur_dsp_line)>=LINELEN-bd.f.enter_spaces)
  320.       { msg_message(M_LONG_LINE);
  321.         goto unchange_ret;
  322.       }
  323.   /*}}}  */
  324.   append_needed_spaces(bd.m.overwrite);
  325.   /*}}}  */
  326.   if (!bd.m.overwrite)
  327.    /*{{{  shift right*/
  328.    {
  329.      /*{{{  check long line*/
  330.      if (   (txt_len>=LINELEN-bd.f.enter_spaces)
  331.          || (bd.m.dialect.typ==F_C_TDS && txt_len>=TDS_LEN-bd.f.enter_spaces) )
  332.       { trailing_spaces(cur_dsp_line);
  333.         txt_len=ustrlen(cur_dsp_line);
  334.         if (txt_len>=LINELEN-bd.f.enter_spaces)
  335.          { msg_message(M_LONG_LINE);
  336.            goto unchange_ret;
  337.          }
  338.         else if (bd.m.dialect.typ==F_C_TDS && txt_len>=TDS_LEN-bd.f.enter_spaces)
  339.            msg_message(M_TDS_LONG_LINE);
  340.         if (txt_pos>txt_len)
  341.          { txt_pos= -1;
  342.            append_needed_spaces(False);
  343.          }
  344.       }
  345.      /*}}}  */
  346.      /*{{{  insert the character at correct position in line*/
  347.      ustrcpy(line_buffer,cur_dsp_line+txt_pos);
  348.      ustrcpy(cur_dsp_line+txt_pos+1,line_buffer);
  349.      txt_len++;
  350.      /*}}}  */
  351.    }
  352.    /*}}}  */
  353.   cur_dsp_line[txt_pos]=ch;
  354.   refresh_field(bd.scr.cursor.w,bd.m.overwrite,False);
  355.   if (bd.scr.cursor.w<=bd.e.pre_scr_e_pos)
  356.    { bd.e.first_scr_e_pos+=dsp.norm;
  357.      bd.e.pre_scr_e_pos+=dsp.norm;
  358.    }
  359.   field_move_cursor(1);
  360.   return;
  361.  
  362. unchange_ret:
  363.   try_unchange();
  364. }
  365. /*}}}  */
  366. /*{{{  delete__*/
  367. private boolean delete__(void)
  368. {
  369.   if (bd.scr.cursor.w <= ind*dsp.norm + 1)
  370.      return(False);
  371.   else
  372.    { if
  373.       /*{{{  incorrext edit pos*/
  374.       (    bd.scr.cursor.w<=bd.e.first_scr_e_pos
  375.         && bd.scr.cursor.w>bd.e.pre_scr_e_pos
  376.       )
  377.       /*}}}  */
  378.       /*{{{  complain*/
  379.       { try_unchange();
  380.         verbose_msg_message(M_ERR_PO);
  381.       }
  382.       /*}}}  */
  383.      else
  384.       /*{{{  do it*/
  385.       { append_needed_spaces(False);
  386.         field_move_cursor(-1);
  387.         deleted_ch=cur_dsp_line[txt_pos];
  388.         /*{{{  do the delete*/
  389.         { unsigned char *s;
  390.  
  391.           for (s=cur_dsp_line+txt_pos;(*s= *(s+1));s++);
  392.           txt_len--;
  393.         }
  394.         /*}}}  */
  395.         if (bd.scr.cursor.w<=bd.e.pre_scr_e_pos)
  396.          { bd.e.first_scr_e_pos-=dsp.norm;
  397.            bd.e.pre_scr_e_pos-=dsp.norm;
  398.          }
  399.         refresh_field(bd.scr.cursor.w,True,False);
  400.       }
  401.       /*}}}  */
  402.      return(True);
  403.    }
  404. }
  405. /*}}}  */
  406. /*{{{  field_edit*/
  407. public TOKEN field_edit(void)
  408. {
  409.   /*{{{  declarations*/
  410.   TOKEN ch;
  411.   boolean field_key;
  412.   change_status old_status;
  413.   boolean force_line_flush;
  414.   /*}}}  */
  415.  
  416.   /*{{{  prepare editing field*/
  417.   force_line_flush= !bd.m.full_shift;
  418.   proc_to_edit_pos();
  419.   if (bd.m.file_changed_status!=unchanged_file)
  420.      bd.m.file_changed_status=changed_once;
  421.   old_status=bd.m.file_changed_status;
  422.   ind = bd.f.current->indent;
  423.   ori_assert(bd.f.enter_spaces>=0,"fieldedit: enter_spaces>=0");
  424.   txt_len=ustrlen(cur_dsp_line);
  425.   if (txt_len > LINELEN-bd.f.enter_spaces)
  426.      exit_origami(r_ocl_err,get_msg(M_LONG_LINE));
  427.   txt_pos=field_scr2txt(bd.f.enter_spaces,bd.scr.cursor.w,cur_dsp_line);
  428.   if (txt_pos>=0)
  429.      bd.scr.cursor.w=txt2scr(bd.f.enter_spaces,txt_pos,cur_dsp_line);
  430.   /* check, if behind LINELEN, if other lines uses multichar displayed
  431.    * characters, therefor:
  432.    */ field_move_cursor(0);
  433.   /*{{{  handle highlighting*/
  434.   switch ((high_type=get_highlight(*bd.f.current)))
  435.    { case c_f_highlight:
  436.      case m_f_highlight:
  437.         high_lim=(LINELEN+2)*max_dsp;
  438.         bd.scr.cur_shift_w= -1;
  439.         break;
  440.      case c_m_highlight:
  441.         high_lim=bd.e.makefold_indent;
  442.         bd.scr.cur_shift_w= -1;
  443.         break;
  444.      case f_m_highlight:
  445.         high_lim=0;
  446.         bd.scr.cur_shift_w= -1;
  447.         break;
  448.      default:
  449.         high_lim= -1;
  450.    }
  451.   /*}}}  */
  452.   /*}}}  */
  453.   do
  454.    { title_op(CHGX);
  455.      /*{{{  get the next operation*/
  456.      curr_c=(txt_pos==-1 || txt_pos==txt_len) ? ' ' : cur_dsp_line[txt_pos];
  457.      /*{{{  maybe user-signal*/
  458. #     ifdef USER_SIGNAL
  459.        user_signal_handle();
  460. #     endif
  461.      /*}}}  */
  462.      do
  463.       {
  464.         /*{{{  handle signals*/
  465. #        if defined(MGR)
  466.            if (win_changed)
  467.             { ch=O_REFRESH;
  468.               break;
  469.             }
  470. #        endif
  471.         if (sig_count)
  472.          { push_macro(sig_macro);
  473.            ocl_msg("pushing %d signals",sig_count);
  474.            sig_count=0;
  475.          }
  476.         /*}}}  */
  477.         /*{{{  show cursor, maybe shift remaining screen*/
  478.         restore_cursor(force_line_flush);
  479.         force_line_flush=False;
  480.         if (restore_shift(bd.scr.cur_shift_w))
  481.            restore_cursor(False);
  482.         /*}}}  */
  483.         ori_assert(bd.scr.cur_shift_w>=0,"negative shift");
  484.         ch=edit_key();
  485.       }
  486.      while (!valid_key(ch));
  487.      field_key = valid_field_key(ch);
  488.      /*}}}  */
  489.      if (field_key)
  490.       { int old_x;
  491.  
  492.         /*{{{  store information for block-selections*/
  493.         old_x=bd.scr.cursor.w;
  494.         /*}}}  */
  495.         /*{{{  handle command*/
  496.         no_message();
  497.         if (ch>=O_NOP)
  498.          /*{{{  a fieldedit command*/
  499.            switch (ch)
  500.             {
  501.               /*{{{  M_BEGIN_OF_LINE*/
  502.               case M_BEGIN_OF_LINE: {
  503.                 int po=0;
  504.                 unsigned char *t=cur_dsp_line;
  505.  
  506.                 while (*t==' ' || *t=='\t') {t++;po++;}
  507.                 macro_tag= *t ? (txt2scr(bd.f.enter_spaces,po,cur_dsp_line)==bd.scr.cursor.w)
  508.                               : bd.scr.cursor.w==ind+1;
  509.                 break;
  510.               }
  511.               /*}}}  */
  512.               /*{{{  M_TOP_OF_FOLD*/
  513.               case M_TOP_OF_FOLD: {
  514.                 macro_tag=(bd.f.current==bd.f.head->next);
  515.                 break;
  516.               }
  517.               /*}}}  */
  518.               /*{{{  M_BOT_OF_FOLD*/
  519.               case M_BOT_OF_FOLD: {
  520.                 macro_tag=(bd.f.current==bd.f.tail);
  521.                 break;
  522.               }
  523.               /*}}}  */
  524.               /*{{{  M_TEST_CHAR (LOW/HIGH/ ) _C SET*/
  525.               case M_TEST_CHAR_SET:
  526.               case M_TEST_CC:
  527.               case M_TEST_L_CC:
  528.               case M_TEST_H_CC:
  529.               case M_TEST_CHAR_LOW:
  530.               case M_TEST_CHAR_HIGH:
  531.               case M_TEST_CHAR:
  532.                  do_cc_compare(curr_c,ch);
  533.                  break;
  534.               /*}}}  */
  535.               /*{{{  M_TEST_STR*/
  536.               case M_TEST_STR:
  537.                  do_str_compare((txt_pos==-1 || txt_pos==txt_len)?empty_text:(cur_dsp_line+txt_pos));
  538.                  break;
  539.               /*}}}  */
  540.               /*{{{  M_STORE_C*/
  541.               case M_STORE_C:
  542.                  ocl_var[get_arg("store-char-var")].v=curr_c;
  543.                  break;
  544.               /*}}}  */
  545.               /*{{{  M_END_OF_LINE*/
  546.               case M_END_OF_LINE:
  547.                  if (txt_len>ind)
  548.                   { unsigned char *x;
  549.                     int i=txt_len;
  550.  
  551.                     if (txt_pos==-1) { macro_tag=True;break; }
  552.                     x=cur_dsp_line+(txt_len-1);
  553.                     while (i-- && (*x==' ' || *x=='\t')) x--;
  554.                     macro_tag=(x<(cur_dsp_line+txt_pos));
  555.                   }
  556.                  else
  557.                     macro_tag=True;
  558.                  break;
  559.               /*}}}  */
  560.               /*{{{  M_GO_COUNTER_X_POS*/
  561.               case M_GO_COUNTER_X_POS:
  562.                { int diff;
  563.  
  564.                  diff=  scr2txt(bd.f.enter_spaces,ocl_var[get_arg("goto-x-target")].v,cur_dsp_line)
  565.                       - (txt_pos==-1?scr2txt(bd.f.enter_spaces,bd.scr.cursor.w,cur_dsp_line):txt_pos);
  566.                  field_move_cursor(diff);
  567.                  break;
  568.                }
  569.               /*}}}  */
  570.               /*{{{  M_POS_TO_COUNTER*/
  571.               case M_POS_TO_COUNTER:
  572.                  ocl_var[get_arg("store-pos-target")].v= bd.scr.cursor.w;
  573.                  break;
  574.               /*}}}  */
  575.               /*{{{  O_FILE_C*/
  576.               case O_FILE_C:
  577.                  if (txt_pos!=-1 && (curr_c==' ' || curr_c=='\t'))
  578.                   { unsigned char *s;
  579.  
  580.                     /*{{{  look for pathname*/
  581.                     for (s=cur_dsp_line+txt_pos-1;;)
  582.                        if (s==cur_dsp_line)
  583.                           break;
  584.                        else if (*--s==' ' || *s=='\t')
  585.                         { s++;
  586.                           break;
  587.                         }
  588.                     /*}}}  */
  589.                     /*{{{  set 0 to indicate end of filename*/
  590.                     cur_dsp_line[txt_pos]='\0';
  591.                     /*}}}  */
  592.                     if (!*do_file_c((char*)s))
  593.                        try_unchange();
  594.                     /*{{{  restore deleted tail of current line*/
  595.                     if (txt_pos!=txt_len) cur_dsp_line[txt_pos]=curr_c;
  596.                     /*}}}  */
  597.                   }
  598.                  break;
  599.               /*}}}  */
  600.               /*{{{  O_START_OF_LINE*/
  601.               case O_START_OF_LINE:
  602.                { if (txt_len>ind)
  603.                   { unsigned char *x=cur_dsp_line;
  604.                     int o=0;
  605.  
  606.                     while (*x==' ' || *x=='\t') { o++;x++; }
  607.                     if (!*x) o=ind;
  608.                     field_move_cursor(
  609.                       o-(  (txt_pos==-1)
  610.                          ? scr2txt(bd.f.enter_spaces,bd.scr.cursor.w,cur_dsp_line)
  611.                          : txt_pos));
  612.                   }
  613.                  else
  614.                     field_move_cursor(ind+1-bd.scr.cursor.w);
  615.                  break;
  616.                }
  617.               /*}}}  */
  618.               /*{{{  O_END_OF_LINE*/
  619.               case O_END_OF_LINE: {
  620.                 unsigned char *x=cur_dsp_line+(txt_len-1);
  621.                 int i=txt_len;
  622.  
  623.                 if (txt_len)
  624.                    while (*x==' ' || *x=='\t')
  625.                     { x--;
  626.                       i--;
  627.                     }
  628.                 if (txt_pos==-1)
  629.                    txt_pos=scr2txt(bd.f.enter_spaces,bd.scr.cursor.w,cur_dsp_line);
  630.                 field_move_cursor((i>ind ? i : ind)-txt_pos);
  631.                 /*{{{  maybe correct the position*/
  632.                 if
  633.                  (    bd.scr.cursor.w<bd.e.first_scr_e_pos
  634.                    && bd.e.first_scr_e_pos<LINELEN-bd.f.enter_spaces
  635.                  )
  636.                    field_move_cursor((bd.e.first_scr_e_pos-bd.scr.cursor.w)/dsp.norm);
  637.                 /*}}}  */
  638.                 break;
  639.               }
  640.               /*}}}  */
  641.               /*{{{  O_LEFT*/
  642.               case O_LEFT:
  643.                  field_move_cursor(-1);
  644.                  break;
  645.               /*}}}  */
  646.               /*{{{  O_RIGHT*/
  647.               case O_RIGHT:
  648.                  field_move_cursor(1);
  649.                  break;
  650.               /*}}}  */
  651.               /*{{{  O_DELETE*/
  652.               case O_DELETE: {
  653.                 field_key=delete__();
  654.                 break;
  655.               }
  656.               /*}}}  */
  657.               /*{{{  O_RETURN*/
  658.               case O_RETURN:   /* cr */
  659.                  switch (bd.m.select_mode)
  660.                   { case fold_selection:
  661.                     case unmark_fold_selection:
  662.                     case lim_pseudo_fold_selection:
  663.                     case lim_reg_selection:
  664.                     case lim_block_selection:
  665.                     case lim_nodrawn_selection:
  666.                        msg_message(M_NOFOLDKEY);
  667.                        break;
  668.                     default:
  669.                        /*{{{  do and break, if possible*/
  670.                        ori_assert(bd.f.cur_line_typ==get_linetyp(*bd.f.current),"%d %d check cur_linetyp");
  671.                        if
  672.                         (    bd.scr.cursor.w>bd.e.pre_scr_e_pos
  673.                           || (    !(bd.f.cur_line_typ&NOT_FOLD)
  674.                                && bd.scr.cursor.w==bd.e.pre_scr_e_pos
  675.                              )
  676.                         )
  677.                         { int first_c;
  678.                           unsigned char *first_txt;
  679.  
  680.                           /*{{{  fill exact with spaces*/
  681.                           /*{{{  cut trailing spaces*/
  682.                           trailing_spaces(cur_dsp_line);
  683.                           txt_len=ustrlen(cur_dsp_line);
  684.                           if (txt_pos>=txt_len) txt_pos= -1;
  685.                           /*}}}  */
  686.                           append_needed_spaces(False);
  687.                           /*}}}  */
  688.                           /*{{{  first_c=first-non-space*/
  689.                           for
  690.                            ( first_c=0,first_txt=cur_dsp_line
  691.                            ;    first_c<txt_pos
  692.                              && (*first_txt==' ' || *first_txt=='\t')
  693.                            ; first_c++,first_txt++
  694.                            );
  695.                           /*}}}  */
  696.                           if
  697.                            (   (    bd.f.current!=bd.f.tail
  698.                                  || bd.scr.cursor.w==1
  699.                                )
  700.                             && (   txt_pos==txt_len
  701.                                 || (   !(bd.f.cur_line_typ&START_ENTER_FILED)
  702.                                     && (   bd.f.cur_line_typ&NOT_FOLD
  703.                                         || (    txt_pos==first_c
  704.                                              && !(bd.f.cur_line_typ&START_ENTER_FOLD)
  705.                                            )
  706.                                         || bd.scr.cursor.w>=bd.e.first_scr_e_pos
  707.                                        )
  708.                                    )
  709.                                )
  710.                            )
  711.                            /*{{{  do the return*/
  712.                            { bd.e.split_line = txt_pos>first_c;
  713.                              bd.e.part_line=proc_new_element();
  714.                              if (!(bd.f.cur_line_typ&END_FOLD))
  715.                                 bd.e.part_line->indent = ind;
  716.                              else
  717.                                 bd.e.part_line->indent =
  718.                                     bd.f.current->x.fold.other_end->indent
  719.                                    -bd.f.current->x.fold.other_end->x.fold.UU.U1.indent;
  720.                              /*{{{  maybe splitt the line*/
  721.                              if (bd.e.split_line)
  722.                               { set_data
  723.                                  ( bd.e.part_line,
  724.                                    cur_dsp_line+txt_pos,
  725.                                    bd.f.cur_line_typ&NOT_FOLD
  726.                                  );
  727.                                 cur_dsp_line[txt_pos]='\0';
  728.                                 txt_len=txt_pos;
  729.                                 refresh_field(bd.scr.cursor.w,True,False);
  730.                                 field_move_cursor((first_c<=ind?ind:first_c)-txt_pos);
  731.                               }
  732.                              /*}}}  */
  733.                              ustrcpy(line_buffer,cur_dsp_line+ind);
  734.                              ustrcpy(line_buffer+((ind<first_c)?(first_c-ind):0),get_data(bd.e.part_line));
  735.                              trailing_spaces(line_buffer);
  736.                              set_data(bd.e.part_line,line_buffer,True);
  737.                              field_key = False;
  738.                              break;
  739.                            }
  740.                            /*}}}  */
  741.                         }
  742.                        /*}}}  */
  743.                     unchange_err_po:
  744.                        try_unchange();
  745.                        verbose_msg_message(M_ERR_PO);
  746.                        break;
  747.                   }
  748.                  break;
  749.               /*}}}  */
  750.               /*{{{  O_TOGGLE_CASE*/
  751.               case O_TOGGLE_CASE:
  752.                  if
  753.                   (    bd.scr.cursor.w<bd.e.first_scr_e_pos
  754.                     && bd.scr.cursor.w>bd.e.pre_scr_e_pos
  755.                   )
  756.                     goto unchange_err_po;
  757.                  append_needed_spaces(True);
  758.                  if (isalpha(curr_c))
  759.                    cur_dsp_line[txt_pos]=islower(curr_c)?toupper(curr_c):tolower(curr_c);
  760.                  refresh_field(bd.scr.cursor.w,False,False);
  761.                  break;
  762.               /*}}}  */
  763.               /*{{{  O_A_VIEW*/
  764.               case O_A_VIEW:
  765.                  init_buffer.m.user_view=
  766.                  init_buffer.m.read_only=
  767.                  bd.m.user_view=
  768.                  bd.m.read_only=True;
  769.                  title_op(CHGTITLE);
  770.                  break;
  771.               /*}}}  */
  772.               /*{{{  O_D_VIEW*/
  773.               case O_D_VIEW:
  774.                  init_buffer.m.user_view=
  775.                  init_buffer.m.read_only=
  776.                  bd.m.user_view=
  777.                  bd.m.read_only=False;
  778.                  title_op(CHGTITLE);
  779.                  break;
  780.               /*}}}  */
  781.               /*{{{  O_A_OVER*/
  782.               case O_A_OVER:
  783.                  init_buffer.m.overwrite=True;
  784.                  if (!bd.m.overwrite)
  785.                   { bd.m.overwrite=True;
  786.                     title_op(CHGTITLE);
  787.                   }
  788.                 break;
  789.               /*}}}  */
  790.               /*{{{  O_D_OVER*/
  791.               case O_D_OVER:
  792.                  init_buffer.m.overwrite=False;
  793.                  if (bd.m.overwrite)
  794.                   { init_buffer.m.overwrite=bd.m.overwrite=False;
  795.                     title_op(CHGTITLE);
  796.                   }
  797.                  break;
  798.               /*}}}  */
  799.               /*{{{  O_A_HASH*/
  800.               case O_A_HASH:
  801.                  if (!bd.m.hash_shift)
  802.                   { bd.m.hash_shift=True;
  803.                     title_op(CHGTITLE);
  804.                   }
  805.                  else
  806.                     try_unchange();
  807.                  init_buffer.m.hash_shift=True;
  808.                  break;
  809.               /*}}}  */
  810.               /*{{{  O_D_HASH*/
  811.               case O_D_HASH:
  812.                  if (bd.m.hash_shift)
  813.                   { bd.m.hash_shift=False;
  814.                     title_op(CHGTITLE);
  815.                   }
  816.                  else
  817.                     try_unchange();
  818.                  init_buffer.m.hash_shift=False;
  819.                  break;
  820.               /*}}}  */
  821.               /*{{{  default*/
  822.               default: break;
  823.               /*}}}  */
  824.             }
  825.          /*}}}  */
  826.         else
  827.            insert_(ch);
  828.         /*}}}  */
  829.         /*{{{  maybe return to higher level, to handle block selections*/
  830.         switch (bd.m.select_mode)
  831.          { case lim_block_selection:
  832.            case block_selection:
  833.               if (field_key && old_x!=bd.scr.cursor.w)
  834.                { ch=O_PROMPT;
  835.                  field_key=False;
  836.                }
  837.            default:
  838.               break;
  839.          }
  840.         /*}}}  */
  841.       }
  842.    }
  843.   while (field_key);
  844.   if (bd.m.file_changed_status!=old_status)
  845.    { trailing_spaces(cur_dsp_line);
  846.      proc_from_edit_pos();
  847.    }
  848.   return ch;
  849. }
  850. /*}}}  */
  851.